package com.drink.yan.svc.service;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.drink.yan.core.mapper.*;
import com.drink.yan.intf.define.YanCommissionCalcTypeE;
import com.drink.yan.intf.define.YanCommissionStatusE;
import com.drink.yan.intf.define.YanUserTypeE;
import com.drink.yan.intf.entity.YanCommission;
import com.drink.yan.intf.entity.YanCommissionRule;
import com.drink.yan.intf.vo.CommissionSummaryVo;
import com.drink.yan.intf.vo.CommissionUserVo;
import com.drink.yan.intf.vo.CommissionVo;
import com.drink.yan.web.rest.req.cmd.CommissionInAccountCmd;
import com.drink.yan.web.rest.req.cmd.CommissionInPayCmd;
import com.drink.yan.web.rest.req.qry.UserCommissionQry;
import com.drink.yan.web.rest.req.qry.PageCommissionQry;
import com.meta.act.app.service.ISysDictTypeService;
import com.meta.framework.common.utils.SecurityUtils;
import com.meta.framework.define.DelFlagEnum;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.math.BigDecimal;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.Optional;

/**
 * java类简单作用描述
 *
 * @Title:
 * @Package: com.drink.yan.svc.service.
 * @Author: M.simple
 * @Remark: The modified content
 * @CreateDate: 2023-12-09 23:54
 * @Version: v2.0
 */
@Service
public class YanCommissionService extends ServiceImpl<YanCommissionMapper, YanCommission> {

	@Resource
	private YanActivityMapper yanActivityMapper;

	@Resource
	private YanTaskMapper yanTaskMapper;

	@Resource
	private YanUserDetailMapper yanUserDetailMapper;

	@Resource
	private YanCommissionRuleMapper yanCommissionRuleMapper;

	@Resource
	private ISysDictTypeService iSysDictTypeService;


	public CommissionSummaryVo summary(UserCommissionQry qry) {

		CommissionSummaryVo commissionSummaryVo = new CommissionSummaryVo();

		qry.setCommissionStatus(YanCommissionStatusE.can_pay.getCode());
		commissionSummaryVo.setCanPayAmount(this.baseMapper.sumAmmount(qry));
		qry.setCommissionStatus(YanCommissionStatusE.already_pay.getCode());
		commissionSummaryVo.setAlreadyPayAmount(this.baseMapper.sumAmmount(qry));
		qry.setCommissionStatus(null);
		commissionSummaryVo.setTotalAmount(this.baseMapper.sumAmmount(qry));
		qry.setCommissionStatus(YanCommissionStatusE.in_account.getCode());
		commissionSummaryVo.setInAccountAmount(this.baseMapper.sumAmmount(qry));
		//BigDecimal amount = this.baseMapper.sumAmmount(qry);

		if(YanUserTypeE.agency.getCode().equals(qry.getUserType())){

			Integer signUserNum = yanActivityMapper.countMyActivitySignUser(qry.getUserId());
			commissionSummaryVo.setSignUserNum(signUserNum);

			Integer taskDealNum = yanTaskMapper.countMyTaskDealNum(qry.getUserId());
			commissionSummaryVo.setCompleteTaskNum(taskDealNum);

			Integer studentNum = this.yanUserDetailMapper.countStudentNum(qry.getUserId());
			commissionSummaryVo.setStudentNum(studentNum);

			Integer buyCourseNum = this.yanUserDetailMapper.agencyCountBuyCourseNum(qry.getUserId());
			commissionSummaryVo.setBuyCourseNum(buyCourseNum);
		}
		return commissionSummaryVo;
	}

	public List<CommissionVo> listCommission(UserCommissionQry qry) {

		Map<String, String> map = iSysDictTypeService.selectDictMapByType("yan_commission_status");
		List<CommissionVo> commissionVos = this.baseMapper.listCommission(qry);
		commissionVos.forEach(x->{
			x.setCommissionStatusName(map.get(x.getCommissionStatus()));
		});
		return commissionVos;
	}

	public List<CommissionVo> listCommissionVo(PageCommissionQry qry) {

		return this.baseMapper.listCommissionVo(qry);
	}

	public BigDecimal sumAmount(UserCommissionQry qry) {

		return this.baseMapper.sumAmmount(qry);
	}

	public YanCommission generateCommission(YanCommission yanCommission) {

		if(checkExistCommission(yanCommission)){
			return yanCommission;
		}

		YanCommissionRule commissionRule = getCommissionRule(yanCommission.getUserType(), yanCommission.getCommissionType());
		if(Objects.isNull(yanCommission.getAmount())){
			if(YanCommissionCalcTypeE.amount.getCode().equals(commissionRule.getCalculateType())){
				yanCommission.setAmount(commissionRule.getCalculateValue());
			}else if(YanCommissionCalcTypeE.rate.getCode().equals(commissionRule.getCalculateType())){
				yanCommission.setAmount(yanCommission.getBusinessAmount().multiply(commissionRule.getCalculateValue().divide(new BigDecimal(100))));
			}
		}
		yanCommission.setCreateBy(yanCommission.getStudentId());

		this.baseMapper.insert(yanCommission);
		return yanCommission;
	}

	private boolean checkExistCommission(YanCommission yanCommission) {

		//判断佣金是否已经存在
		LambdaQueryWrapper<YanCommission> queryWrapper = new LambdaQueryWrapper<>();
		queryWrapper.eq(YanCommission::getCommissionType, yanCommission.getCommissionType());
		queryWrapper.eq(YanCommission::getUserType, yanCommission.getUserType());
		queryWrapper.eq(YanCommission::getBusinessKey, yanCommission.getBusinessKey());
		queryWrapper.eq(YanCommission::getBusinessSubKey, yanCommission.getBusinessSubKey());
		queryWrapper.eq(YanCommission::getUserId, yanCommission.getUserId());
		queryWrapper.eq(YanCommission::getDelFlag, DelFlagEnum.O.getCode());
		YanCommission commission = this.getOne(queryWrapper);
		if(Objects.nonNull(commission) && Objects.nonNull(commission.getId())){
			return true;
		}
		return false;
	}

	public List<CommissionUserVo> listCommissionUser(UserCommissionQry qry) {

		return yanUserDetailMapper.listCommissionUser(qry);
	}

	public YanCommission inAccount(CommissionInAccountCmd cmd) {

		YanCommission yanCommission = baseMapper.selectById(cmd.getCommissionId());
		yanCommission.setInAccountSuccTime(cmd.getInAccountSuccTime());
		yanCommission.setCommissionStatus(YanCommissionStatusE.can_pay.getCode());

		this.baseMapper.updateById(yanCommission);

		return yanCommission;
	}

	public YanCommission inPay(CommissionInPayCmd cmd) {

		YanCommission yanCommission = baseMapper.selectById(cmd.getCommissionId());
		yanCommission.setAlreadyPaySuccTime(cmd.getAlreadyPaySuccTime());
		yanCommission.setCommissionStatus(YanCommissionStatusE.already_pay.getCode());

		this.baseMapper.updateById(yanCommission);

		return yanCommission;
	}

	public List<YanCommissionRule> listCommissionRule() {

		LambdaQueryWrapper<YanCommissionRule> queryWrapper = new LambdaQueryWrapper<>();
		queryWrapper.eq(YanCommissionRule::getDelFlag, DelFlagEnum.O.getCode());
		return this.yanCommissionRuleMapper.selectList(queryWrapper);
	}

	public YanCommissionRule getCommissionRule(Long ruleId) {

		return this.yanCommissionRuleMapper.selectById(ruleId);
	}

	public YanCommissionRule getCommissionRule(String userType, String commissionType) {

		LambdaQueryWrapper<YanCommissionRule> queryWrapper = new LambdaQueryWrapper<>();
		queryWrapper.eq(YanCommissionRule::getUserType, userType);
		queryWrapper.eq(YanCommissionRule::getCommissionType, commissionType);
		queryWrapper.eq(YanCommissionRule::getDelFlag, DelFlagEnum.O.getCode());
		queryWrapper.last("limit 1");

		return this.yanCommissionRuleMapper.selectOne(queryWrapper);
	}

	public YanCommissionRule saveRule(YanCommissionRule cmd) {

		if(Objects.isNull(cmd.getRuleId())){
			cmd.setCreateBy(SecurityUtils.getUserId());
			this.yanCommissionRuleMapper.insert(cmd);
		}else{
			YanCommissionRule commissionRule = getCommissionRule(cmd.getRuleId());
			Optional.ofNullable(cmd.getCalculateValue()).ifPresent(commissionRule::setCalculateValue);
			Optional.ofNullable(cmd.getCalculateType()).ifPresent(commissionRule::setCalculateType);
			Optional.ofNullable(cmd.getCommissionType()).ifPresent(commissionRule::setCommissionType);
			Optional.ofNullable(cmd.getUserType()).ifPresent(commissionRule::setUserType);
			this.yanCommissionRuleMapper.updateById(commissionRule);
			cmd = commissionRule;
		}

		return cmd;
	}
}
